"""
慢性病风险预测与智能干预系统 - Flask主应用
"""

from flask import Flask, render_template, request, jsonify
from flask_cors import CORS
import pandas as pd
import numpy as np
import json
import os
from datetime import datetime, timedelta

# 导入自定义模块
from models.xgboost_model import XGBoostPredictor
from models.lstm_model import LSTMModelWrapper
from models.model_fusion import ModelFusion
from data.preprocessing import DataPreprocessor
from utils.shap_explainer import SHAPExplainer
from utils.intervention_recommender import InterventionRecommender

app = Flask(__name__)
CORS(app)

# 全局变量存储模型
xgboost_model = None
lstm_model = None
fusion_model = None
preprocessor = None
shap_explainer = None
intervention_recommender = None

def initialize_models():
    """初始化所有模型和组件"""
    global xgboost_model, lstm_model, fusion_model, preprocessor, shap_explainer, intervention_recommender
    
    print("正在初始化模型...")
    
    # 初始化数据预处理器
    preprocessor = DataPreprocessor()
    
    # 初始化XGBoost模型
    xgboost_model = XGBoostPredictor()
    
    # 初始化LSTM模型
    lstm_model = LSTMModelWrapper()
    
    # 初始化模型融合器
    fusion_model = ModelFusion(xgboost_model, lstm_model)
    
    # 初始化SHAP解释器
    shap_explainer = SHAPExplainer()
    
    # 初始化干预推荐器
    intervention_recommender = InterventionRecommender()
    
    print("模型初始化完成！")

@app.route('/')
def index():
    """主页"""
    return render_template('index.html')

@app.route('/doctor')
def doctor_dashboard():
    """医生端仪表板"""
    return render_template('doctor_dashboard.html')

@app.route('/user')
def user_dashboard():
    """用户端仪表板"""
    return render_template('user_dashboard.html')

@app.route('/api/predict', methods=['POST'])
def predict_risk():
    """风险预测API"""
    try:
        data = request.json
        
        # 验证输入数据
        if not data:
            return jsonify({'error': '未提供输入数据'}), 400
        
        # 预处理输入数据
        processed_data = preprocessor.preprocess_user_input(data)
        
        # 进行风险预测
        prediction_result = fusion_model.predict(processed_data)
        
        # 生成SHAP解释
        shap_explanation = shap_explainer.explain_prediction(processed_data, prediction_result)
        
        # 生成干预建议
        intervention_suggestions = intervention_recommender.get_recommendations(
            prediction_result, data
        )
        
        # 构建响应
        response = {
            'success': True,
            'prediction': prediction_result,
            'shap_explanation': shap_explanation,
            'intervention_suggestions': intervention_suggestions,
            'timestamp': datetime.now().isoformat()
        }
        
        return jsonify(response)
        
    except Exception as e:
        return jsonify({'error': f'预测过程中发生错误: {str(e)}'}), 500

@app.route('/api/upload_data', methods=['POST'])
def upload_data():
    """数据上传API"""
    try:
        if 'file' not in request.files:
            return jsonify({'error': '未找到上传文件'}), 400
        
        file = request.files['file']
        if file.filename == '':
            return jsonify({'error': '未选择文件'}), 400
        
        # 读取上传的文件
        if file.filename.endswith('.csv'):
            df = pd.read_csv(file)
        elif file.filename.endswith('.xlsx'):
            df = pd.read_excel(file)
        else:
            return jsonify({'error': '不支持的文件格式，请上传CSV或Excel文件'}), 400
        
        # 预处理数据
        processed_df = preprocessor.preprocess_batch_data(df)
        
        # 批量预测
        predictions = []
        for _, row in processed_df.iterrows():
            prediction = fusion_model.predict(row.to_dict())
            predictions.append(prediction)
        
        # 统计结果
        risk_distribution = {
            'low_risk': sum(1 for p in predictions if p['risk_level'] == 'low'),
            'medium_risk': sum(1 for p in predictions if p['risk_level'] == 'medium'),
            'high_risk': sum(1 for p in predictions if p['risk_level'] == 'high')
        }
        
        response = {
            'success': True,
            'total_records': len(predictions),
            'risk_distribution': risk_distribution,
            'predictions': predictions[:10],  # 只返回前10条结果
            'message': f'成功处理{len(predictions)}条记录'
        }
        
        return jsonify(response)
        
    except Exception as e:
        return jsonify({'error': f'数据处理过程中发生错误: {str(e)}'}), 500

@app.route('/api/health_metrics', methods=['GET'])
def get_health_metrics():
    """获取健康指标趋势数据"""
    try:
        # 模拟生成健康指标数据
        dates = pd.date_range(start='2024-01-01', end='2024-12-31', freq='D')
        
        # 生成模拟血压数据
        systolic_bp = np.random.normal(120, 15, len(dates))
        diastolic_bp = np.random.normal(80, 10, len(dates))
        
        # 生成模拟血糖数据
        blood_glucose = np.random.normal(100, 20, len(dates))
        
        # 生成模拟BMI数据
        bmi = np.random.normal(23, 3, len(dates))
        
        metrics_data = {
            'dates': [d.strftime('%Y-%m-%d') for d in dates],
            'systolic_bp': systolic_bp.tolist(),
            'diastolic_bp': diastolic_bp.tolist(),
            'blood_glucose': blood_glucose.tolist(),
            'bmi': bmi.tolist()
        }
        
        return jsonify(metrics_data)
        
    except Exception as e:
        return jsonify({'error': f'获取健康指标数据时发生错误: {str(e)}'}), 500

@app.route('/api/risk_factors', methods=['GET'])
def get_risk_factors():
    """获取风险因素分析数据"""
    try:
        # 模拟风险因素数据
        risk_factors = {
            'smoking': {'impact': 0.25, 'description': '吸烟'},
            'family_history': {'impact': 0.20, 'description': '家族史'},
            'high_blood_pressure': {'impact': 0.18, 'description': '高血压'},
            'high_glucose': {'impact': 0.15, 'description': '高血糖'},
            'obesity': {'impact': 0.12, 'description': '肥胖'},
            'sedentary_lifestyle': {'impact': 0.10, 'description': '久坐生活方式'}
        }
        
        return jsonify(risk_factors)
        
    except Exception as e:
        return jsonify({'error': f'获取风险因素数据时发生错误: {str(e)}'}), 500

if __name__ == '__main__':
    # 创建必要的目录
    os.makedirs('templates', exist_ok=True)
    os.makedirs('static/css', exist_ok=True)
    os.makedirs('static/js', exist_ok=True)
    os.makedirs('models', exist_ok=True)
    os.makedirs('data', exist_ok=True)
    os.makedirs('utils', exist_ok=True)
    
    # 初始化模型
    initialize_models()
    
    # 启动应用
    print("启动慢性病风险预测系统...")
    print("访问地址: http://localhost:5000")
    app.run(debug=True, host='0.0.0.0', port=5000)
